package com.zhumo.sz.provider;

import com.google.common.base.CaseFormat;
import com.zhumo.sz.common.annotation.TransientSink;

import java.lang.reflect.Field;
import java.util.List;
import java.util.Map;

/**
 * @author zhumo
 * @time 2023-09-18 16:20:22
 * @comment 用于Mybatis 批量插入数据,转换要求，实体类和Mysql字段名 必须符合orm映射规范,
 * 如果实体对象的实体bean带有 transink 注解,则跳过该属性，一般用于自增主键和少量描述性字段
 * 如果需要使用这个方法，还需要要求实体bean的类名和mysql的表名满足orm映射的关系的
 * 比如: subway_station_info:SubwayTrafficInfo
 *     * insert into my_table ( col1, col2, col3)  values  (val1, val2, val3), (val1, val2, val3), (val1, val2, val3)
 *     sb.append("#{list[" + i + "]." + fieldName + "},");
 * 实质上就是返回一条批量insert的sql
 */
public class BatchInsertProvider {

    public <T> String batchInsert(Map<String, List<T>> map) {
        List<T> list = map.get("list");
        StringBuilder sqlBuilder = new StringBuilder("insert into ");
        sqlBuilder.append(getTableName(list.get(0))).append(" (");
        for (Field field : list.get(0).getClass().getDeclaredFields()) {
            field.setAccessible(true);
            TransientSink annotation = field.getAnnotation(TransientSink.class);
            if (annotation == null) {
                sqlBuilder.append(CaseFormat.LOWER_CAMEL.to(CaseFormat.LOWER_UNDERSCORE, field.getName())).append(",");
            }
        }
        sqlBuilder.deleteCharAt(sqlBuilder.length()-1).append(") values ");

        Field[] fields = list.get(0).getClass().getDeclaredFields();
        for (int i = 0; i < list.size(); i++) {
            sqlBuilder.append("(");
            for (Field field : fields) {
                field.setAccessible(true);
                if (field.getAnnotation(TransientSink.class) == null) {
                    String fieldName = field.getName();
                    String methodName = "get" + fieldName.substring(0, 1).toUpperCase() + fieldName.substring(1); //获取get方法名
                    sqlBuilder.append("#{list[" + i + "]." + fieldName + "},");
                }
            }
            sqlBuilder.deleteCharAt(sqlBuilder.length()-1);
            sqlBuilder.append("),");
        }
        sqlBuilder.deleteCharAt(sqlBuilder.length() - 1); // 去掉最后一个逗号
        return sqlBuilder.toString();
    }

    /**
     * 获取表名
     * @param t 插入实体类型
     * @param <T> 泛型
     * @return insert sql
     */
    private <T> String getTableName(T t) {
        Class<?> tClass = t.getClass();
        return CaseFormat.LOWER_CAMEL.to(CaseFormat.LOWER_UNDERSCORE,tClass.getSimpleName());
    }

    /**
     * 拼接value 占位符
     * @param t
     * @param <T>
     * @return
     */
    private <T> String getValuesIndex(T t){
        StringBuilder valueBuilder = new StringBuilder("(");
        Class<?> tClass = t.getClass();
        Field[] fields = tClass.getDeclaredFields();
        for (Field field : fields) {
            field.setAccessible(true);
            if (field.getAnnotation(TransientSink.class) == null){
                valueBuilder.append("#{").append(field.getName()).append("},");
            }
        }
        valueBuilder.deleteCharAt(valueBuilder.length()-1).append(")"); //去掉最后一个逗号
        return valueBuilder.toString();
    }

//    public static void main(String[] args) {
//        BatchInsertProvider batchInsertProvider = new BatchInsertProvider();
//        ArrayList<SubwayStationInfo> subwayStationInfos = new ArrayList<>();
//        for (int i = 0; i < 10; i++) {
//            subwayStationInfos.add(new SubwayStationInfo());
//        }
//        HashMap<String, List<SubwayStationInfo>> stringListHashMap = new HashMap<>();
//        stringListHashMap.put("list",subwayStationInfos);
//        System.out.println(batchInsertProvider.batchInsert(stringListHashMap));
//    }
    /*
    insert into subway_station_info columns (id,line_code,line_name,site_name,site_code,oper_code,site_introduced)
    values (#{id},#{lineCode},#{lineName},#{siteName},#{siteCode},#{operCode},#{siteIntroduced})
     */
}
